local TechTree = GLOBAL.require("techtree")
local blueprint_suffix_name = "_blueprint"


-- 物品掉落表
local loot_tables = {
    -- 草掉落
    grass = {"cutgrass", "rope"},
    -- 常青树掉落
    evergreen = {"log", "board"},
    evergreen_normal = {"log", "board"},
    evergreen_tall = {"log", "board"},
    evergreen_short = {"log", "board"},
    evergreen_sparse = {"log", "board"},
    evergreen_sparse_normal = {"log", "board"},
    evergreen_sparse_tall = {"log", "board"},
    evergreen_sparse_short = {"log", "board"},
    -- 多枝树
    twiggytree = {"twigs", "log", "board"},
    twiggy_normal = {"twigs", "log", "board"},
    twiggy_tall = {"twigs", "log", "board"},
    twiggy_short = {"twigs", "log", "board"},
    -- 月树
    moon_tree_short = {"log", "board", "moon_tree_blossom"},
    moon_tree_normal = {"log", "board", "moon_tree_blossom"},
    moon_tree_tall = {"log", "board", "moon_tree_blossom"},
    moon_tree = {"log", "board", "moon_tree_blossom"},
    -- 蘑菇
    blue_mushroom = {"blue_cap"},
    red_mushroom = {"red_cap"},
    green_mushroom = {"green_cap"},
    mushtree_short = {"green_cap"},
    mushtree_medium = {"red_cap"},
    mushtree_tall = {"blue_cap"},
    -- 芦苇
    reeds = {"cutreeds"},
    -- 华栗树
    deciduoustree = {"log", "board"},
    deciduoustree_normal = {"log", "board"},
    deciduoustree_short = {"log", "board"},
    deciduoustree_tall = {"log", "board"},
    -- 被烧的
    deciduoustree_burnt = {"charcoal"},
--     -- 浮木来源
--     driftwood_small1 = {"driftwood_log"},
--     driftwood_small2 = {"driftwood_log"},
--     driftwood_tall = {"driftwood_log"},
    -- 完全正常的树
    livingtree = {"livinglog"},
    -- 烧了的树
    evergreen_burnt = {"charcoal"},
    -- 小树枝掉落
    sapling = {"twigs"},
    sapling_moon = {"twigs"},
    -- 常青树树人
    leif = {"livinglog"},
    -- 岩石带月岩
    rock_moon  = {"rocks", "cutstone", "flint", "moonrocknugget"},
    -- 蝴蝶
    butterfly = {"butterflywings"},
    -- 花
    flower = {"petals"},
    planted_flower = {"petals"},
    flower_evil = {"petals_evil"},
    -- 荧光果植物
    flower_cave = {"lightbulb"},
    flower_cave_double = {"lightbulb"},
    flower_cave_triple = {"lightbulb"},
    -- 发光蓝莓
    wormlight_plant = {"wormlight"},
    -- 鼹鼠
    mole = {"mole"},
    -- 石化树
    rock_petrified_tree_short = {"rocks", "cutstone", "flint", "nitre"},
    rock_petrified_tree_med = {"rocks", "cutstone", "flint", "nitre"},
    rock_petrified_tree_tall = {"rocks", "cutstone", "flint", "nitre"},
    rock_petrified_tree = {"rocks", "cutstone", "flint", "nitre"},
    -- 大理石灌木
    marbleshrub_short = {"marble"},
    marbleshrub_normal = {"marble"},
    marbleshrub_tall = {"marble"},
    -- 岩石
    rock1 = {"rocks", "cutstone", "flint", "nitre"},
    -- 岩石带黄金
    rock2 = {"rocks", "cutstone", "flint", "goldnugget"},
    -- 岩石只有石头
    rock_flintless = {"rocks", "cutstone"},
    -- 迷你冰川
    rock_ice = {"ice"},
    -- 碎石（洞穴）
--     rubble
    -- 石笋：
    stalagmite_low = {"rocks", "flint", "cutstone"},
    stalagmite_med = {"rocks", "flint", "cutstone"},
    stalagmite_full = {"rocks", "flint", "cutstone", "goldnugget", "bluegem", "redgem"},
    stalagmite_tall_low = {"rocks", "flint", "cutstone"},
    stalagmite_tall_med = {"rocks", "flint", "cutstone", "goldnugget"},
    stalagmite_tall_full = {"rocks", "flint", "cutstone", "goldnugget", "bluegem", "redgem"},
    spiderhole_rock = {"rocks", "flint", "cutstone", "goldnugget", "bluegem", "redgem"},
    -- 盐堆
    saltstack = {"saltrock"},
    -- 影怪
    crawlinghorror = {"nightmarefuel"},
    crawlingnightmare = {"nightmarefuel"},
    terrorbeak = {"nightmarefuel"},
    nightmarebeak = {"nightmarefuel"},
    oceanhorror = {"nightmarefuel"},
    -- 蜜蜂
    bee = {"stinger"},
    killerbee = {"stinger"},
    -- 蜂窝
    beehive = {"honeycomb"},
    wasphive = {"honeycomb"},
    -- 钢羊
    spat = {"steelwool", "meat"},
    -- 考拉象
    koalefant_summer = {"trunk_summer", "meat"},
    koalefant_winter = {"trunk_winter", "meat"},
    -- 猪猪
    pigman = {"meat", "pigskin"},
    -- 蜘蛛
    spider = {"silk", "spidergland"},
    spider_warrior = {"silk", "spidergland"},
    spider_hider = {"silk", "spidergland"},
    spider_spitter = {"silk", "spidergland"},
    spider_dropper = {"silk", "spidergland"},
    spider_moon = {"silk", "spidergland"},
    -- 狗哥
    hound = {"houndstooth"},
    mutatedhound = {"houndstooth"},
    firehound = {"houndstooth", "redgem"},
    icehound = {"houndstooth", "redgem"},
    -- 牛
    beefalo = {"meat", "beefalowool"},
    -- 缀食者
    sluroer = {"slurper_pelt"},
    -- 洞穴蠕虫：
    worm = {"wormlight"},
    -- 兔人
    bunnyman = {"meat", "carrot", "manrabbit_tail", "beardhair"},
    -- 幻猫
    catcoon = {"meat", "coontail"},
    -- 蝙蝠
    bat = {"batwing"},
    -- 齿轮怪
    knight = {"gears"},
    bishop = {"gears"},
    knight_nightmare = {"gears"},
    bishop_nightmare = {"gears"},
    rook_nightmare = {"gears"},
    -- 坏鱼
    spoiled_fish_small = {"spoiled_food", "boneshard"},
    spoiled_fish = {"spoiled_food", "boneshard"},
    -- 海象
    walrus = {"walrus_tusk", "meat"},
    little_walrus = {"walrus_tusk", "meat"},
    -- 电羊
    lightninggoat = {"meat", "lightninggoathorn"},
    -- 触手
    tentacle = {"tentaclespots"},
    -- 以后补充
}


local function CanBlueprintSpecificRecipe(recipe)
    -- 人物自带科技解锁
    if recipe.builder_tag ~= nil then
        for k, v in pairs(recipe.level) do
            if v > 0 then
                -- 解锁
                recipe.level = TechTree.Create()
                break
            end
        end
    end
    --Exclude crafting station and character specific
    if recipe.nounlock or recipe.builder_tag ~= nil then
        return false
    end
    for k, v in pairs(recipe.level) do
        if v > 0 then
            return true
        end
    end
    --Exclude TECH.NONE
    return false
end


local inspectable_description = {
    evergreen = "木板蓝图 0.01  路牌蓝图 0.01",
    worm = "鼹鼠帽蓝图 0.3",
    leif = "黄金斧头蓝图 0.3",
    rock_flintless = "锚套装蓝图 0.1 暖石蓝图 0.025",
    deciduoustree = "木墙蓝图 0.02 木板蓝图 0.005",
    grass = "绳子蓝图 0.006",
    bat = "蝙蝠棒蓝图 0.06",
    beequeen = "船补丁蓝图 1 蜂箱蓝图 1",
    pigman = "火腿棒蓝图 0.015",
    rock1 = "烹饪锅锅蓝图 0.025 电子元件蓝图 0.005 暖石蓝图 0.025",
    rock2 = "矿工帽蓝图 0.1 电子元件蓝图 0.01 暖石蓝图 0.025",
    frog = "空浇水壶蓝图 0.1 雨量计蓝图	0.08",
    bee = "强心针蓝图 0.016",
    stalagmite = "园艺锄蓝图 0.025 电子元件蓝图 0.005",
    eyeofterror = "衣柜蓝图	1 帐篷蓝图 1",
    spider = "治疗药膏蓝图 0.1",
    walrus = "催眠吹箭蓝图 0.25",
    blueamulet = "眼球伞蓝图 1 寒冰护符蓝图 1 吸热火坑蓝图 1",
    dragonfly = "暖石蓝图 1",
    mossling = "避雷导线蓝图 0.01 天气风向标蓝图 0.01 避雷针蓝图 0.01",
    moose = "避雷导线蓝图 1 天气风向标蓝图 1 避雷针蓝图 1",
    cookiecutter = "饼干切割机帽子蓝图 0.25",
    rock_ice = "冰帽蓝图 0.1"
}

local blueprintConfig = {
    rock_ice = {
        icehat = 0.1
    },
    cookiecutter = {
        cookiecutterhat = 0.25
    },
    mossling = {
        mastupgrade_lightningrod_item = 0.01,
        staff_tornado = 0.01,
        lightning_rod = 0.01
    },
    walrus = {
        blowdart_sleep = 0.25
    },
    spider = {
        healingsalve = 0.1
    },
    evergreen = {
        boards = 0.01,
        homesign = 0.01
    },
    worm = {
        molehat = 0.3
    },
    leif = {
        goldenaxe = 0.3
    },
    rock_flintless = {
        anchor_item = 0.1,
        heatrock = 0.025
    },
    deciduoustree = {
        -- 桦树掉落木墙的概率0.02
        wall_wood_item = 0.02,
        boards = 0.005
    },
    grass = {
        -- 收集草掉落草绳的概率
        rope = 0.006
    },
    bat = {
        -- 蝙蝠棒
        batbat = 0.06
    },
    pigman = {
        hambat = 0.015
    },
    rock1 = {
        cookpot = 0.025,
        transistor = 0.005,
        heatrock = 0.025
    },
    rock2 = {
        minerhat = 0.1,
        transistor = 0.1,
        heatrock = 0.025
    },
    frog = {
        wateringcan = 0.1,
        rainometer = 0.08,
    },
    bee = {
        lifeinjector = 0.016
    },
    stalagmite = {
        farm_hoe = 0.025,
        transistor = 0.005
    },

}

-- 保存所有蓝图的表
local blueprints = {}

-- boss掉落蓝图配置
local blueprintConfigBoss = {
    -- 麋鹿鹅
    moose = {
        special_drop_weights = 0.3,
        blueprints = {
            mastupgrade_lightningrod_item = 1,
            staff_tornado = 1,
            lightning_rod = 1
        }
    },
    -- 龙鹰
    dragonfly = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.5,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            -- 龙鹰宝箱
            dragonflychest = 0.8,
            -- 紫宝石合成蓝图
            purplegem = 0.2,
            -- 龙鹰地板蓝图
            turf_dragonfly = 0.1,
            -- 鳞甲蓝图
            armordragonfly = 1,
            heatrock = 1
        }
    },
    -- 蜂后
    beequeen = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.5,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            -- 船补丁
            boatpatch = 1,
            -- 蜡
            beeswax = 1,
            -- 蜂箱
            beebox = 1
        }
    },
    -- 巨鹿
    deerclops = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.5,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            eyebrellahat = 1,
            blueamulet = 1,
            coldfirepit = 1
        }
    },
    -- 克劳斯, 克劳斯有两次，掉落需要改下
    klaus = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.2,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            amulet = 0.2
        }
    },
    -- 蓝鹿
    deer_blue = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = -1,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            icestaff = 1
        }
    },
    -- 红鹿
    deer_red = {
            -- 掉落未学习过的蓝图权重
            special_drop_weights = -1,
            -- 掉落击杀龙鹰专属蓝图
            blueprints = {
                firestaff = 1
            }
    },
    -- 熊大
    bearger = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.5,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            beargervest = 1,
            bearger_fur = 0.2,
            icepack = 1,
        }
    },
    -- 蚂蚁
    antlion = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.5,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            saltbox = 1,
            sculptingtable = 1,
        }
    },
    -- 小海象，??? 这东西是boss？
    little_walrus = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = -1,
        -- 掉落击杀专属蓝图
        blueprints = {
            cane = 1
        }
    },
    -- 恐怖眼
    eyeofterror = {
        -- 掉落未学习过的蓝图权重
        special_drop_weights = 0.5,
        -- 掉落击杀龙鹰专属蓝图
        blueprints = {
            wardrobe = 1,
            tent = 1
        }
    }
}

-- 加载世界中所有蓝图
local load_blueprints = function ()
    -- 下面代码加载所有蓝图
    for prefab_name, recipe in pairs(GLOBAL.AllRecipes) do
        if CanBlueprintSpecificRecipe(recipe) then
            -- 该物品名称, 没有"_blueprint"后缀
            prefab_name = string.lower(prefab_name or "NONAME")
            table.insert(blueprints, prefab_name)
        end
    end
end

-- boss特殊掉落
local function boss_drop_blueprints(inst, player, config)
    -- 随机数
    local r = math.random()
    -- 判断是否特殊掉落
    if r < config["special_drop_weights"] then
        -- 掉落玩家未学习过的蓝图
        local index = math.floor(r * #blueprints) + 1
        for i = 1, #blueprints, 1 do
            local recipe = blueprints[index]
            if not player.components.builder:KnowsRecipe(recipe) then
                -- 有些物品没有该组件，尝试添加如: 恶魔花就没
                if inst.components.lootdropper == nil then
                    inst:AddComponent("lootdropper")
                end
                -- 打印掉落蓝图
                print("[boss掉落蓝图]" .. recipe .. blueprint_suffix_name)
                -- 掉落蓝图
                inst.components.lootdropper:SpawnLootPrefab(recipe .. blueprint_suffix_name)
                break
            end
            -- 寻找下一个该玩家未学习过的蓝图
            index = (index + 1) % #blueprints + 1
        end
    end

    -- boss掉落
    r = math.random()
    local boss_blueprints = config["blueprints"]

    for recipe, drop_weight in pairs(boss_blueprints) do
        if not player.components.builder:KnowsRecipe(recipe) then
             -- 有些物品没有该组件，尝试添加如: 恶魔花就没
             if inst.components.lootdropper == nil then
                inst:AddComponent("lootdropper")
            end
            if r < drop_weight then
                -- 掉落蓝图
                inst.components.lootdropper:SpawnLootPrefab(recipe .. blueprint_suffix_name)
            end

            r = math.random()
        end
    end

end


local get_drop_blueprints = function (prefab_name, description)
    if prefab_name then
        local n = string.len(prefab_name)

        for i = 1, n, 1 do
            local index_key = string.sub(prefab_name, 1, n-i+1)
            if description[index_key] ~= nil then
                return description[index_key]
            end
        end
    end

    return nil
end

local function chance_drop_blueprints(inst, player)
    -- 获取prefab, 掉落的材料
    if player == nil or not player:HasTag("player") or player.components.builder == nil then
        return
    end
    -- 中文名称
    local prefab_chinese_name = inst.name
    -- 英文名称
    local prefab_name = inst.prefab

    if prefab_chinese_name == nil or prefab_name == nil then
        return
    end
    -- boss 特殊掉落
    if blueprintConfigBoss[prefab_name] ~= nil then
        boss_drop_blueprints(inst, player, blueprintConfigBoss[prefab_name])
        return
    end

    local drop_blueprints = get_drop_blueprints(prefab_name, blueprintConfig) or {}

    -- 随机数
    local r = math.random()
    -- 遍历掉落蓝图
    for recipe, chance in pairs(drop_blueprints) do
        print(prefab_name .. prefab_chinese_name .. "-开始掉落蓝图-" .. recipe)
        if not player.components.builder:KnowsRecipe(recipe) then
            player.components.guaranteed:addBlueprintTriggers(recipe, 1)
            -- 判断玩家是否触发保底
            local count = player.components.guaranteed:getBlueprintTriggers(recipe)
            -- chance一定不能为0
            local max_count = 1 / chance
            -- 触发保底
            if count >= max_count then
                r = 0
            end

            if r < chance then
                -- 有些物品没有该组件，尝试添加如: 恶魔花就没
                if inst.components.lootdropper == nil then
                    inst:AddComponent("lootdropper")
                end
                -- 掉落蓝图
                inst.components.lootdropper:SpawnLootPrefab(recipe .. blueprint_suffix_name)
                player.components.guaranteed:resetBlueprintTriggers(recipe)
            end
            r = math.random()
        end
    end
end

-- 世界初始化之后加载蓝图
AddSimPostInit(load_blueprints)

-- 人物保底机制
AddPlayerPostInit(function(inst)
    if not inst.components.level then
        -- 给人物添加上组件guaranteed
        inst:AddComponent("guaranteed")
    end
end)

-- 给工作组件注册
AddComponentPostInit("workable", function (Workable)
    local old_WorkedBy = Workable.WorkedBy
    function Workable:WorkedBy(worker, numworks)
        -- 执行旧方法
        old_WorkedBy(self, worker, numworks)
        -- 工作完成，掉落蓝图
        if self.workleft <= 0 then
            chance_drop_blueprints(self.inst, worker)
        end
    end
end)


local get_description = function (inst, description)
    if inst and inst.prefab then
        local n = string.len(inst.prefab)

        for i = 1, n, 1 do
            local index_key = string.sub(inst.prefab, 1, n-i+1)
            if description[index_key] ~= nil then
                return description[index_key]
            end
        end
    end

    return nil
end

-- 给检测组件注册
AddComponentPostInit("inspectable", function (Inspectable)
    local old_GetDescription = Inspectable.GetDescription
    function Inspectable:GetDescription(viewer)
        -- 执行旧方法
        local desc, filter_context, author = old_GetDescription(self, viewer)
        local change_desc = get_description(self.inst, inspectable_description)

        if change_desc ~= nil then
            desc = change_desc
        end

        return desc, filter_context, author
    end
end)

-- 给采集组件注册
AddComponentPostInit("pickable", function (Pickable)
    local old_Pick = Pickable.Pick
    function Pickable:Pick(picker)
        -- 执行旧方法
        old_Pick(self, picker)
        chance_drop_blueprints(self.inst, picker)
    end
end)

-- 给攻击组件注册
AddComponentPostInit("combat", function (Combat)
    local old_GetAttacked = Combat.GetAttacked
    function Combat:GetAttacked(attacker, damage, weapon, stimuli)
        -- 执行旧方法
        old_GetAttacked(self, attacker, damage, weapon, stimuli)
        -- 生物击杀死亡才掉落蓝图
        if self.inst.components.health:IsDead() then
            chance_drop_blueprints(self.inst, attacker)
        end
    end
end)

-- 一本科技禁用
AddPrefabPostInit("researchlab", function(inst)
    if GLOBAL.TheWorld.ismastersim and inst.components.prototyper then
        inst.components.prototyper.trees = TechTree.Create()
    end
end)

-- 二本科技禁用
AddPrefabPostInit("researchlab2", function(inst)
    if GLOBAL.TheWorld.ismastersim and inst.components.prototyper then
        inst.components.prototyper.trees = TechTree.Create()
    end
end)

-- 三本科技禁用
AddPrefabPostInit("researchlab3", function(inst)
    if GLOBAL.TheWorld.ismastersim and inst.components.prototyper then
        inst.components.prototyper.trees = TechTree.Create()
    end
end)

-- 四本科技禁用
AddPrefabPostInit("researchlab4", function(inst)
    if GLOBAL.TheWorld.ismastersim and inst.components.prototyper then
        inst.components.prototyper.trees = TechTree.Create()
    end
end)

-- 智囊团科技禁用
AddPrefabPostInit("seafaring_prototyper", function(inst)
    if GLOBAL.TheWorld.ismastersim and inst.components.prototyper then
        inst.components.prototyper.trees = TechTree.Create()
    end
end)

